/*
 * Copyright 2008 the original author or authors.
 * 
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 * 
 *      http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.ccsoft.mc.core.impl;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.ccsoft.mc.core.Reference;
import org.ccsoft.mc.core.Service;
import org.ccsoft.mc.core.ServiceBundle;
import org.ccsoft.mc.core.ServiceChangeListener;
import org.ccsoft.mc.core.ServiceContext;
/**
 * 
 * @author Chao Cai
 *
 * the class has implemented the basic operations ot the cache used in the project
 */
public class BaseCache {
	protected Set<ServiceBundle> cache=new HashSet<ServiceBundle>();
	protected Set<ServiceChangeListener> listeners=new HashSet<ServiceChangeListener>();
	protected void notifyListenersServiceReady(ServiceBundle obj){
		for (ServiceChangeListener listen:listeners){
			listen.onServiceReady(obj);
		}
	}
	public void add(ServiceBundle obj){
		boolean ret=cache.add(obj) ;
		if (ret){
			notifyListenersServiceReady(obj);
		}
	}	
	public void remove(ServiceBundle obj){
		cache.remove(obj);
	}
	public Object getServiceByName(String name) {
		for (ServiceBundle bundle:cache){
			if (bundle.getComponentName().equals(name)){
				return bundle.getInstance();
			}
		}
		return null;
	}


	public void registerServiceChangeListener(ServiceChangeListener listener) {
		listeners.add(listener);
		
	}
	public Object getServiceByType(String type) {
		for (ServiceBundle bundle:cache){
			List<Service> services=bundle.getServices();
			for (Service service:services){
				if (service.getInterfaceName().equals(type)){
					return  bundle.getInstance();
				}
			}
		}
		return null;
	}
	public  List getServicesByType(String type) {
		List ret=new ArrayList ();
		for (ServiceBundle bundle:cache){
			List<Service> services=bundle.getServices();
			for (Service service:services){
				if (service.getInterfaceName().equals(type)){
					ret.add(  bundle.getInstance());
				}
			}
		}
		return ret;
		
	}
	public Object getServiceByType(String type, String name) {
		for (ServiceBundle bundle:cache){
			List<Service> services=bundle.getServices();
			for (Service service:services){
				if (service.getInterfaceName().equals(type)&&(bundle.getComponentName().equals(name))){
					return  bundle.getInstance();
				}
			}
		}
		return null;
	}
	private ServiceBundle getBundleByName(String name){
		for (ServiceBundle bundle:cache){
			if (bundle.getComponentName().equals(name)){
				return bundle;
			}
		}
		return null;
	}
	public List<ServiceBundle> findBundlesByReference(String reference){
		List<ServiceBundle> ret=new ArrayList<ServiceBundle> ();
		for (ServiceBundle bundle:cache){
			List<Reference> references=bundle.getReferences();
			for (Reference ref:references){
				if (ref.getInterfaceName().equals(reference)){
					ret.add(bundle);
				}
			}
		}
		return ret;
	}
	public Set<ServiceBundle> getServiceBundles(){
		return cache;
	}
	public void removeBundleByName(String name){
		ServiceBundle bundle=this.getBundleByName(name);
		bundle=null;
	}
}
